package com.canaan.business.schedule;

import cn.hutool.core.collection.CollUtil;
import com.canaan.business.common.enums.agv.AgvEnum;
import com.canaan.business.common.enums.inOutStock.*;
import com.canaan.business.common.enums.storehouse.StorehouseStockStatusEnum;
import com.canaan.business.common.helper.BeanHelper;
import com.canaan.business.common.helper.EmptyStockHelper;
import com.canaan.business.domain.basic.StockStrategy;
import com.canaan.business.domain.basic.WmsStorehouseLocation;
import com.canaan.business.domain.bill.*;
import com.canaan.business.domain.inOutStock.OutStockBill;
import com.canaan.business.domain.inOutStock.OutStockBillDetail;
import com.canaan.business.domain.inOutStock.SplitBill;
import com.canaan.business.domain.inOutStock.SplitBillDetail;
import com.canaan.business.domain.storehouse.WmsStorehouseStock;
import com.canaan.business.domain.vo.OutStockQueryVo;
import com.canaan.business.domain.vo.OutStockResultVo;
import com.canaan.business.domain.vo.WmsStorehouseStockVo;
import com.canaan.business.service.agv.IAgvTaskDispatchService;
import com.canaan.business.service.basic.IStockStrategyService;
import com.canaan.business.service.basic.IWmsStorehouseLocationService;
import com.canaan.business.service.bill.*;
import com.canaan.business.service.inOutStock.IOutStockBillDetailService;
import com.canaan.business.service.inOutStock.IOutStockBillService;
import com.canaan.business.service.inOutStock.ISplitBillDetailService;
import com.canaan.business.service.inOutStock.ISplitBillService;
import com.canaan.business.service.storehouse.IStorehouseStockStrategyService;
import com.canaan.business.service.storehouse.IWmsStockOutStockStrategyService;
import com.canaan.business.service.storehouse.IWmsStorehouseStockService;
import com.canaan.common.core.redis.RedisCache;
import com.canaan.common.utils.StringUtils;
import com.canaan.common.utils.TableNoUtil;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;

@Slf4j
@Component("AutoOutBillSchedule")
public class AutoOutBillSchedule {
    @Resource
    private RedisCache redisCache;

    @Resource
    private IStorehouseStockStrategyService storehouseStockStrategyService;
    @Resource
    private IWmsStorehouseStockService storehouseStockService;
    @Resource
    private IWmsStorehouseLocationService wmsStorehouseLocationService;
    @Resource
    private EmptyStockHelper emptyStockHelper;
    @Resource
    private IAgvTaskDispatchService agvTaskDispatchService;
    @Resource
    private IOutStockBillService outStockBillService;
    @Resource
    private IOutStockBillDetailService outStockBillDetailService;
    @Resource
    private ISplitBillService splitBillService;
    @Resource
    private ISplitBillDetailService splitBillDetailService;
    @Resource
    private IBillDetailRecordService billDetailRecordService;
    @Resource
    private IAdjustOutBillService adjustOutBillService;
    @Resource
    private IAdjustOutBillDetailService adjustOutBillDetailService;
    @Resource
    private IModulationOutBillService modulationOutBillService;
    @Resource
    private IModulationOutBillDetailService modulationOutBillDetailService;
    @Resource
    private IPurchaseReturnBillService purchaseReturnBillService;
    @Resource
    private IPurchaseReturnBillDetailService purchaseReturnBillDetailService;
    @Resource
    private ITrayService trayService;
    @Resource
    private ITrayDetailService trayDetailService;
    @Resource
    private  ITrayProductFreezeService trayProductFreezeService;
    @Resource
    private ITrayProductFreezeDetailService trayProductFreezeDetailService;
    @Resource
    private IStockStrategyService stockStrategyService;
    @Resource
    private BeanHelper beanHelper;

    @ApiOperation(value = "预出库", notes = "预出库")
    @Transactional(propagation = Propagation.REQUIRES_NEW,rollbackFor = Exception.class)
    public void preOutStock(){
        boolean result=handleAdjustOutBill();
        if(result){
            return;
        }
        result=handleModulationOutBill();
        if(result){
            return;
        }
        handleReceiveReturnBill();
    }

    /**
     * 处理调拨出库单
     * @return
     */
    private boolean handleAdjustOutBill(){
        AdjustOutBill query=new AdjustOutBill();
        query.setStatus(OutOrderStatusEnum.NEW.getCode());
        query.setDelFlag("0");
        List<AdjustOutBill> adjustOutBills=adjustOutBillService.selectAdjustOutBillList(query);
        if(adjustOutBills==null||adjustOutBills.size()==0){
            return false;
        }
        adjustOutBills.sort(Comparator.comparing(O->O.getCreateTime()));
        AdjustOutBill adjustOutBill=adjustOutBills.get(0);
        String stockStatus=adjustOutBill.getStockStatus();
        //查询调拨出库单明细
        List<String> productNos=new ArrayList<>();
        List<Long> productCounts=new ArrayList<>();
        AdjustOutBillDetail detailQuery=new AdjustOutBillDetail();
        detailQuery.setBillNo(adjustOutBill.getNo());
        detailQuery.setDelFlag("0");
        List<AdjustOutBillDetail> details=adjustOutBillDetailService.selectAdjustOutBillDetailList(detailQuery);
        for (AdjustOutBillDetail detail :details){
            productNos.add(detail.getProductNo());
            productCounts.add(detail.getQty());
        }
        //OutStockQueryVo赋值
        OutStockQueryVo outStockQueryVo=new OutStockQueryVo();
        outStockQueryVo.setStockStatus(stockStatus);
        outStockQueryVo.setProductNos(productNos);
        outStockQueryVo.setProductCounts(productCounts);
        outStockQueryVo.setBillNo(adjustOutBill.getNo());
        outStockQueryVo.setBillType(ErpBillTypeEnum.ADJUST_OUT.getCode());
        outStockQueryVo.setCellCode(adjustOutBill.getAddress());
        outStockQueryVo.setShortMatch(adjustOutBill.getShortMatch());
        /*OutStockResultVo outStockResultVo= analyseOutStock(outStockQueryVo);
        for (AdjustOutBillDetail item:details) {
            List<OutStockBillDetail> outStockBillDetails =outStockResultVo.getOutStockBillDetails().stream().filter(O->O.getProductNo().equals(item.getProductNo())).collect(Collectors.toList());
            if(outStockBillDetails.size()!=0){
                OutStockBillDetail outStockBillDetail=outStockBillDetails.get(0);
                item.setBatchNo(outStockBillDetail.getBatchNo());
            }
        }
        adjustOutBillDetailService.batchUpdateAdjustOutBillDetail(details);
         */
        preOutStockExecute(outStockQueryVo);
        adjustOutBill.setStatus(OutOrderStatusEnum.WAITING_PICK.getCode());
        adjustOutBillService.updateAdjustOutBill(adjustOutBill);
        log.info("处理"+adjustOutBill.getNo()+"预处理完成");
        return true;
    }

    /**
     * 处理出库调整单
     * @return
     */
    private boolean handleModulationOutBill(){
        ModulationOutBill query=new ModulationOutBill();
        query.setStatus(OutOrderStatusEnum.NEW.getCode());
        query.setDelFlag("0");
        List<ModulationOutBill> modulationOutBills =modulationOutBillService.selectModulationOutBillList(query);
        if(modulationOutBills ==null|| modulationOutBills.size()==0){
            return false;
        }
        modulationOutBills.sort(Comparator.comparing(O->O.getCreateTime()));
        ModulationOutBill outBill= modulationOutBills.get(0);
        //查询调拨出库单明细
        List<String> productNos = new ArrayList<>();
        List<Long> productCounts = new ArrayList<>();
        String stockStatus = outBill.getStockStatus();
        ModulationOutBillDetail detailQuery = new ModulationOutBillDetail();
        detailQuery.setBizNo(outBill.getBizNo());
        detailQuery.setDelFlag("0");
        List<ModulationOutBillDetail> details = modulationOutBillDetailService.selectModulationOutBillDetailList(detailQuery);
        for (ModulationOutBillDetail detail : details) {
            productNos.add(detail.getProductNo());
            productCounts.add(detail.getQty());
        }
        //OutStockQueryVo赋值
        OutStockQueryVo outStockQueryVo = new OutStockQueryVo();
        outStockQueryVo.setStockStatus(stockStatus);
        outStockQueryVo.setProductNos(productNos);
        outStockQueryVo.setProductCounts(productCounts);
        outStockQueryVo.setBillNo(outBill.getBizNo());
        outStockQueryVo.setBillType(ErpBillTypeEnum.MODULATION_OUT.getCode());
        outStockQueryVo.setCellCode(outBill.getCellCode());
        outStockQueryVo.setShortMatch(outBill.getShortMatch());
        /*OutStockResultVo outStockResultVo = analyseOutStock(outStockQueryVo);
        if (CollUtil.isEmpty(outStockResultVo.getOutStockBillDetails())) {
            throw new RuntimeException("调拨出库单" + outBill.getBizNo() + "没有可调拨的库存");
        }
        for (ModulationOutBillDetail item : details) {
            List<OutStockBillDetail> outStockBillDetails = outStockResultVo.getOutStockBillDetails().stream().filter(O -> O.getProductNo().equals(item.getProductNo())).collect(Collectors.toList());
            if (outStockBillDetails.size() != 0) {
                OutStockBillDetail outStockBillDetail = outStockBillDetails.get(0);
                item.setBatchNo(outStockBillDetail.getBatchNo());
            }
        }
        modulationOutBillDetailService.batchUpdateModulationOutBillDetail(details);
         */
        preOutStockExecute(outStockQueryVo);
        outBill.setStatus(OutOrderStatusEnum.WAITING_PICK.getCode());
        modulationOutBillService.updateModulationOutBill(outBill);
        log.info("处理"+outBill.getBizNo()+"预处理完成");
        return true;
    }

    /**
     * 处理采购退货单
     */
    private boolean handleReceiveReturnBill(){
        PurchaseReturnBill query=new PurchaseReturnBill();
        query.setStatus(OutOrderStatusEnum.NEW.getCode());
        query.setDelFlag("0");
        List<PurchaseReturnBill> purchaseReturnBills=purchaseReturnBillService.selectPurchaseReturnBillList(query);
        if(purchaseReturnBills==null||purchaseReturnBills.size()==0){
            return false;
        }
        PurchaseReturnBill purchaseReturnBill=purchaseReturnBills.get(0);
        //查询调拨出库单明细
        List<String> productNos=new ArrayList<>();
        List<Long> productCounts=new ArrayList<>();
        List<String> batchNos=new ArrayList<>();
        String stockStatus=purchaseReturnBill.getStockStatus();
        PurchaseReturnBillDetail detailQuery=new PurchaseReturnBillDetail();
        detailQuery.setOrderNo(purchaseReturnBill.getNo());
        detailQuery.setDelFlag("0");
        List<PurchaseReturnBillDetail> details=purchaseReturnBillDetailService.selectPurchaseReturnBillDetailList(detailQuery);
        for (PurchaseReturnBillDetail detail :details){
            productNos.add(detail.getProductNo());
            productCounts.add(detail.getOrderQty());
            if(StringUtils.isEmpty(detail.getBatchNo())){
                batchNos.add("");
            }else{
                batchNos.add(detail.getBatchNo());
            }
        }
        //OutStockQueryVo赋值
        OutStockQueryVo outStockQueryVo=new OutStockQueryVo();
        outStockQueryVo.setStockStatus(stockStatus);
        outStockQueryVo.setProductNos(productNos);
        outStockQueryVo.setProductCounts(productCounts);
        outStockQueryVo.setBatchNos(batchNos);
        outStockQueryVo.setBillNo(purchaseReturnBill.getNo());
        outStockQueryVo.setBillType(ErpBillTypeEnum.PURCHASE_RETURN.getCode());
        outStockQueryVo.setCellCode(purchaseReturnBill.getCellCode());
        /*OutStockResultVo outStockResultVo=analyseOutStock(outStockQueryVo);
        for (PurchaseReturnBillDetail item:details) {
            List<OutStockBillDetail> outStockBillDetails =outStockResultVo.getOutStockBillDetails().stream().filter(O->O.getProductNo().equals(item.getProductNo())).collect(Collectors.toList());
            if(outStockBillDetails.size() != 0){
                OutStockBillDetail outStockBillDetail=outStockBillDetails.get(0);
                item.setBatchNo(outStockBillDetail.getBatchNo());
            }
        }
        purchaseReturnBillDetailService.batchUpdatePurchaseReturnBillDetail(details);
         */
        preOutStockExecuteLock(outStockQueryVo);
        purchaseReturnBill.setStatus(OutOrderStatusEnum.WAITING_PICK.getCode());
        purchaseReturnBillService.updatePurchaseReturnBill(purchaseReturnBill);
        log.info("处理"+purchaseReturnBill.getNo()+"预处理完成");
        return true;
    }
    /**
     * 预检货
     */
    private OutStockResultVo analyseOutStock(OutStockQueryVo outStockQueryVo){
        String key = "OUT_LOCK";

        //TODO 临时方案锁，后期处理
        String lock = redisCache.getCacheObject(key);
        if (StringUtils.equals(lock, "true")) {
            throw new RuntimeException("有上架任务正在进行中，请稍后再试");
        }
        redisCache.setCacheObject(key, "true");
        OutStockResultVo resultVo;
        try {
            resultVo = analyseOutStockLock(outStockQueryVo);
        } catch (Exception e) {
            e.printStackTrace();
            throw new RuntimeException(e.getMessage());
        } finally {
            //TODO 临时方案
            redisCache.setCacheObject(key, "false");
        }
        return resultVo;
    }

    /**
     * 预检货
     */
    private void preOutStockExecute(OutStockQueryVo outStockQueryVo){
        String key = "OUT_LOCK";

        //TODO 临时方案锁，后期处理
        String lock = redisCache.getCacheObject(key);
        if (StringUtils.equals(lock, "true")) {
            throw new RuntimeException("有上架任务正在进行中，请稍后再试");
        }
        redisCache.setCacheObject(key, "true");
        try {
            preOutStockExecuteLock(outStockQueryVo);
        } catch (Exception e) {
            e.printStackTrace();
            throw new RuntimeException(e.getMessage());
        } finally {
            //TODO 临时方案
            redisCache.setCacheObject(key, "false");
        }
    }

    /**
     * 解析预出库
     */
    private void preOutStockExecuteLock(OutStockQueryVo outStockQueryVo){
        Map<String,Long> resultMap=new HashMap<>();
        for(int i=0;i<outStockQueryVo.getProductNos().size();i++){
            String productNo=outStockQueryVo.getProductNos().get(i);
            Long count=outStockQueryVo.getProductCounts().get(i);
            resultMap.put(productNo,count);
        }
        List<TrayProductFreeze> trayProductFreezeList=trayProductFreezeService.selectTrayProductFreezeListByProductNos(outStockQueryVo);
        analysePreFreezeTrayProduct(trayProductFreezeList,resultMap,outStockQueryVo.getBillNo());
        //调整物料数量
        if(resultMap.size()!=0){
            for(int i=outStockQueryVo.getProductCounts().size()-1;i>=0;i--){
                String productNo=outStockQueryVo.getProductNos().get(i);
                if(resultMap.containsKey(productNo)){
                    Long count=resultMap.get(productNo);
                    List<Long> productCounts= outStockQueryVo.getProductCounts();
                    productCounts.set(i,count);
                }
                else{
                    outStockQueryVo.getProductCounts().remove(i);
                    outStockQueryVo.getProductCounts().remove(i);
                    outStockQueryVo.getBatchNos().remove(i);
                }
            }
           List<WmsStorehouseStockVo> stockProductFreezeList=analyseStockProductFreeze(outStockQueryVo,resultMap);
            for (WmsStorehouseStockVo item :stockProductFreezeList){
                //清空源库位
                WmsStorehouseLocation destLocation= emptyStockHelper.analyseInStock(outStockQueryVo.getBillNo(),"",false,false);
                //锁定源库位
                WmsStorehouseStock sourceStock=storehouseStockService.selectWmsStorehouseStockByLocationNo(item.getStorehouseLocationNo());
                if(sourceStock==null){
                    throw new RuntimeException("源库位"+item.getStorehouseLocationNo()+"不存在库存数据");
                }
                WmsStorehouseLocation sourceLocation=wmsStorehouseLocationService.selectWmsStorehouseLocationByNo(sourceStock.getStorehouseLocationNo());
                if(sourceLocation==null){
                    throw new RuntimeException("源库位"+sourceStock.getStorehouseLocationNo()+"不存在");
                }
                sourceStock.setStatus(StorehouseStockStatusEnum.LOCK.getCode());
                storehouseStockService.updateWmsStorehouseStock(sourceStock);
                //锁定目标库位
                WmsStorehouseStock destStock=storehouseStockService.selectWmsStorehouseStockByLocationNo(destLocation.getNo());
                if(destStock==null){
                    throw new RuntimeException("库位"+destLocation.getNo()+"不存在库存数据");
                }
                destStock.setStatus(StorehouseStockStatusEnum.FREEZE.getCode());
                storehouseStockService.updateWmsStorehouseStock(destStock);
                //创建AGV任务
                agvTaskDispatchService.createTaskDispatch("",sourceLocation,destLocation, AgvEnum.TASK_TYPE.OUT,
                        sourceStock.getContainerNo(),sourceStock.getTrayNo());
                //分析是否调库单
                emptyStockHelper.generateAdjustLocation(sourceLocation.getNo(),sourceLocation.getIsInner(),sourceLocation.getInnerLocation(),item.getNo());
            }
        }
    }

    /**
     * 解析库存的物料
     */
    private List<WmsStorehouseStockVo> analyseStockProductFreeze(OutStockQueryVo outStockQueryVo, Map<String,Long> resultMap){
        List<WmsStorehouseStockVo> wmsStorehouseStockVos;
        StockStrategy stockStrategy=stockStrategyService.selectOutStockDefaultStrategy();
        if(stockStrategy==null){
            wmsStorehouseStockVos=storehouseStockService.selectWmsStorehouseStockListByProductNos(outStockQueryVo);
        }
        else{
            IWmsStockOutStockStrategyService outStockStrategyService =(IWmsStockOutStockStrategyService) beanHelper.getBean(stockStrategy.getClassName());
            if(outStockStrategyService ==null){
                throw new RuntimeException("出库策略"+stockStrategy.getClassName()+"不存在");
            }
            wmsStorehouseStockVos= outStockStrategyService.selectWmsStorehouseStockListByProductNos(outStockQueryVo);
        }
        if(wmsStorehouseStockVos==null||wmsStorehouseStockVos.size()==0){
            throw new RuntimeException("成品库存不足");
        }

        wmsStorehouseStockVos.sort(Comparator.comparing((WmsStorehouseStockVo i)->i.getIsInner())
                .thenComparing(i->i.getQty()).thenComparing(i->i.getBatchNo()));

        List<TrayProductFreeze> productFreezes=new ArrayList<>();
        List<TrayProductFreezeDetail> productFreezeDetails=new ArrayList<>();
        List<WmsStorehouseStockVo> selectedStockVos=new ArrayList<>();
        for (WmsStorehouseStockVo item :wmsStorehouseStockVos){
            if("1".equals(item.getIsSplit())&& StringUtils.isNotEmpty(item.getInnerLocation())){
                WmsStorehouseStock outerStock=storehouseStockService.selectWmsStorehouseStockByLocationNo(item.getInnerLocation());
                if(StringUtils.isNotEmpty(outerStock.getContainerNo())){
                    log.info("里库"+item.getStorehouseLocationNo()+"关联外库"+item.getInnerLocation()+"存在容器");
                    continue;
                }
                if(StorehouseStockStatusEnum.LOCK.getCode().equals(outerStock.getStatus())){
                    log.info("里库"+item.getStorehouseLocationNo()+"关联外库"+item.getInnerLocation()+"状态为已锁定");
                    continue;
                }
            }
            TrayDetail query=new TrayDetail();
            query.setTrayNo(item.getTrayNo());
            query.setDelFlag("0");
            List<TrayDetail> trayDetails=trayDetailService.selectTrayDetailList(query);
            if(trayDetails==null||trayDetails.size()==0){
                continue;
            }
            if(resultMap.size()==0){
                break;
            }
            trayDetails=trayDetails.stream().sorted(Comparator.comparing(TrayDetail::getBatchNo)).collect(Collectors.toList());

            boolean selected=false;
            for(TrayDetail trayDetail:trayDetails) {
                if(!resultMap.containsKey(trayDetail.getProductNo())){
                    continue;
                }
                Long resCount=resultMap.get(trayDetail.getProductNo());
                if(resCount==0){
                    continue;
                }
                TrayProductFreeze trayProductFreeze=new TrayProductFreeze();
                trayProductFreeze.setNo(TableNoUtil.getNo(TrayProductFreeze.class));
                trayProductFreeze.setTrayNo(trayDetail.getTrayNo());
                trayProductFreeze.setStockStatus(trayDetail.getStockStatus());
                trayProductFreeze.setProductNo(trayDetail.getProductNo());
                trayProductFreeze.setStatus(TrayProductFreezeStatus.NEW.getCode());
                trayProductFreeze.setBatchNo(trayDetail.getBatchNo());
                trayProductFreeze.setQty(trayDetail.getQty());
                if(trayDetail.getQty()>resCount) {
                    trayProductFreeze.setFreezeQty(resCount);
                    resultMap.remove(trayDetail.getProductNo());
                }
                //若托盘整托被冻结，则将更新托盘ERP出库单据号
                else if(trayDetail.getQty().equals(resCount)){
                    trayProductFreeze.setFreezeQty(resCount);
                    resultMap.remove(trayDetail.getProductNo());
                    Tray tray=trayService.selectTrayByTrayNo(trayDetail.getTrayNo());
                    if(tray!=null){
                        tray.setErpOutBillNo(outStockQueryVo.getBillNo());
                        trayService.updateTray(tray);
                    }
                }
                else{
                    trayProductFreeze.setFreezeQty(trayDetail.getQty());
                    resultMap.put(trayDetail.getProductNo(),resCount-trayDetail.getQty());
                }
                productFreezes.add(trayProductFreeze);

                TrayProductFreezeDetail freezeDetail=new TrayProductFreezeDetail();
                freezeDetail.setFreezeNo(trayProductFreeze.getNo());
                freezeDetail.setTrayNo(trayDetail.getTrayNo());
                freezeDetail.setProductNo(trayDetail.getProductNo());
                freezeDetail.setBillNo(outStockQueryVo.getBillNo());
                freezeDetail.setQty(trayProductFreeze.getFreezeQty());
                freezeDetail.setStockStatus(trayDetail.getStockStatus());
                productFreezeDetails.add(freezeDetail);
                selected=true;
            }
            if(selected){
                selectedStockVos.add(item);
            }
        }
        trayProductFreezeDetailService.batchInsertTrayProductFreezeDetail(productFreezeDetails);
        if(resultMap.size()!=0){
            StringBuilder str= new StringBuilder();
            for(String productNo:resultMap.keySet()){
                str.append(productNo).append(":").append(resultMap.get(productNo)).append(";");
            }
            throw new RuntimeException("成品库存不足，" + str);
        }
        trayProductFreezeService.batchInsertTrayProductFreeze(productFreezes);
        return selectedStockVos;
    }
    /**
     * 解析已经冻结的托盘物料
     */
    private void analysePreFreezeTrayProduct(List<TrayProductFreeze> trayProductFreezes,Map<String,Long> resultMap,String billNo){
        for (TrayProductFreeze item :trayProductFreezes){
            if(resultMap.size()==0){
                break;
            }
            if(!resultMap.containsKey(item.getProductNo())){
                continue;
            }
            Long resCount=resultMap.get(item.getProductNo());
            if(resCount==0){
                continue;
            }
            if(item.getQty().equals(item.getFreezeQty())){
                continue;
            }
            long qty=0;
            if(item.getQty()-item.getFreezeQty()<resCount) {
                //当前冻结物料还不够
                qty=item.getQty()-item.getFreezeQty();
                item.setFreezeQty(item.getQty());
                resultMap.put(item.getProductNo(),resCount-(item.getQty()-item.getFreezeQty()));
            }
            else{
                qty=resCount;
                //当前冻结物料已经满足需求
                item.setFreezeQty(item.getFreezeQty()+resCount);
                resultMap.remove(item.getProductNo());
            }
            TrayProductFreezeDetail detail=new TrayProductFreezeDetail();
            detail.setFreezeNo(item.getNo());
            detail.setTrayNo(item.getTrayNo());
            detail.setStockStatus(item.getStockStatus());
            detail.setQty(qty);
            detail.setProductNo(item.getProductNo());
            detail.setBillNo(billNo);
            trayProductFreezeDetailService.insertTrayProductFreezeDetail(detail);
        }
        trayProductFreezeService.batchInsertTrayProductFreeze(trayProductFreezes);
    }


    /**
     * 解析出库
     */
    private OutStockResultVo analyseOutStockLock(OutStockQueryVo outStockQueryVo){
        outStockQueryVo.setShortMatch("0");
        //解析得到出库的成品库位
        OutStockResultVo resultVo=storehouseStockStrategyService.selectAllOutStock(outStockQueryVo);

        for (OutStockBill item :resultVo.getOutStockBills()){
            //清空源库位
            WmsStorehouseLocation destLocation= emptyStockHelper.analyseInStock(outStockQueryVo.getBillNo(),"",false,false);
            //锁定源库位
            WmsStorehouseStock sourceStock=storehouseStockService.selectWmsStorehouseStockByLocationNo(item.getSourceLocation());
            if(sourceStock==null){
                throw new RuntimeException("源库位"+item.getSourceLocation()+"不存在库存数据");
            }
            WmsStorehouseLocation sourceLocation=wmsStorehouseLocationService.selectWmsStorehouseLocationByNo(sourceStock.getStorehouseLocationNo());
            if(sourceLocation==null){
                throw new RuntimeException("源库位"+sourceStock.getStorehouseLocationNo()+"不存在");
            }
            sourceStock.setStatus(StorehouseStockStatusEnum.LOCK.getCode());
            storehouseStockService.updateWmsStorehouseStock(sourceStock);
            //锁定目标库位
            WmsStorehouseStock destStock=storehouseStockService.selectWmsStorehouseStockByLocationNo(destLocation.getNo());
            if(destStock==null){
                throw new RuntimeException("库位"+item.getDestLocation()+"不存在库存数据");
            }
            destStock.setStatus(StorehouseStockStatusEnum.FREEZE.getCode());
            storehouseStockService.updateWmsStorehouseStock(destStock);
            item.setDestLocation(destLocation.getNo());
            //创建AGV任务
            agvTaskDispatchService.createTaskDispatch("",sourceLocation,destLocation, AgvEnum.TASK_TYPE.OUT,
                    sourceStock.getContainerNo(),sourceStock.getTrayNo());
            //分析是否调库单
            emptyStockHelper.generateAdjustLocation(sourceLocation.getNo(),sourceLocation.getIsInner(),sourceLocation.getInnerLocation(),item.getNo());
        }
        if(resultVo.getOutStockBills().size()!=0){
            outStockBillService.batchInsertOutStockBill(resultVo.getOutStockBills());
        }
        if(resultVo.getOutStockBillDetails().size()!=0){
            outStockBillDetailService.batchInsertOutStockBillDetail(resultVo.getOutStockBillDetails());
        }
        if(resultVo.getSplitBills().size()!=0){
            splitBillService.batchInsertSplitBill(resultVo.getSplitBills());
        }
        if(resultVo.getSplitBillDetails().size()!=0){
            splitBillDetailService.batchInsertSplitBillDetail(resultVo.getSplitBillDetails());
        }
        if(resultVo.getBillDetailRecords().size()!=0){
            billDetailRecordService.batchInsertBillDetailRecord(resultVo.getBillDetailRecords());
        }
        return resultVo;
    }
}
